From 7c73f2fb02d8b4c11beed0748ad3791af2081800 Mon Sep 17 00:00:00 2001 From: Alexander Larsson Date: Thu, 6 Feb 2020 16:21:54 +0100 Subject: [PATCH] GskPango: Allow specifying a custom shape snapshot handler We will need this for GtkTextView to render the textures in it. --- gtk/gskpango.c | 60 ++++++++++++++++++++++++++++++++++++++++---------- gtk/gskpango.h | 8 +++++++ 2 files changed, 56 insertions(+), 12 deletions(-) diff --git a/gtk/gskpango.c b/gtk/gskpango.c index 0e04a0b95a..5d2eb3c527 100644 --- a/gtk/gskpango.c +++ b/gtk/gskpango.c @@ -45,6 +45,15 @@ gsk_pango_renderer_set_state (GskPangoRenderer *crenderer, crenderer->state = state; } +void +gsk_pango_renderer_set_shape_handler (GskPangoRenderer *crenderer, + GskPangoShapeHandler handler) +{ + g_return_if_fail (GSK_IS_PANGO_RENDERER (crenderer)); + + crenderer->shape_handler = handler; +} + static void get_color (GskPangoRenderer *crenderer, PangoRenderPart part, @@ -240,26 +249,49 @@ gsk_pango_renderer_draw_shape (PangoRenderer *renderer, gpointer shape_renderer_data; double base_x = (double)x / PANGO_SCALE; double base_y = (double)y / PANGO_SCALE; + gboolean handled = FALSE; - cr = gtk_snapshot_append_cairo (crenderer->snapshot, &crenderer->bounds); + if (crenderer->shape_handler) + { + double shape_x = base_x; + double shape_y = (double) (y + attr->logical_rect.y) / PANGO_SCALE; - layout = pango_renderer_get_layout (renderer); - if (!layout) - return; + if (shape_x != 0 || shape_y != 0) + { + gtk_snapshot_save (crenderer->snapshot); + gtk_snapshot_translate (crenderer->snapshot, &GRAPHENE_POINT_INIT (shape_x, shape_y)); + } - shape_renderer = pango_cairo_context_get_shape_renderer (pango_layout_get_context (layout), - &shape_renderer_data); + handled = crenderer->shape_handler (attr, + crenderer->snapshot, + (double)attr->logical_rect.width / PANGO_SCALE, + (double)attr->logical_rect.height / PANGO_SCALE); + if (shape_x != 0 || shape_y != 0) + gtk_snapshot_restore (crenderer->snapshot); + } - if (!shape_renderer) - return; + if (!handled) + { + cr = gtk_snapshot_append_cairo (crenderer->snapshot, &crenderer->bounds); - set_color (crenderer, PANGO_RENDER_PART_FOREGROUND, cr); + layout = pango_renderer_get_layout (renderer); + if (!layout) + return; - cairo_move_to (cr, base_x, base_y); + shape_renderer = pango_cairo_context_get_shape_renderer (pango_layout_get_context (layout), + &shape_renderer_data); - shape_renderer (cr, attr, FALSE, shape_renderer_data); + if (!shape_renderer) + return; - cairo_destroy (cr); + set_color (crenderer, PANGO_RENDER_PART_FOREGROUND, cr); + + cairo_move_to (cr, base_x, base_y); + + shape_renderer (cr, attr, FALSE, shape_renderer_data); + + cairo_destroy (cr); + } } static void @@ -408,6 +440,10 @@ gsk_pango_renderer_acquire (void) } renderer = cached_renderer; + + /* Reset to standard state */ + renderer->state = GSK_PANGO_RENDERER_NORMAL; + renderer->shape_handler = NULL; } else { diff --git a/gtk/gskpango.h b/gtk/gskpango.h index 33ebff422a..bbd3699f43 100644 --- a/gtk/gskpango.h +++ b/gtk/gskpango.h @@ -41,6 +41,11 @@ typedef enum GSK_PANGO_RENDERER_CURSOR } GskPangoRendererState; +typedef gboolean (*GskPangoShapeHandler) (PangoAttrShape *attr, + GdkSnapshot *snapshot, + double width, + double height); + /* * This is a PangoRenderer implementation that translates all the draw calls to * gsk render nodes, using the GtkSnapshot helper class. Glyphs are translated @@ -60,6 +65,7 @@ struct _GskPangoRenderer GdkRGBA *error_color; GskPangoRendererState state; + GskPangoShapeHandler shape_handler; /* house-keeping options */ guint is_cached_renderer : 1; @@ -73,6 +79,8 @@ struct _GskPangoRendererClass GType gsk_pango_renderer_get_type (void) G_GNUC_CONST; void gsk_pango_renderer_set_state (GskPangoRenderer *crenderer, GskPangoRendererState state); +void gsk_pango_renderer_set_shape_handler (GskPangoRenderer *crenderer, + GskPangoShapeHandler handler); GskPangoRenderer *gsk_pango_renderer_acquire (void); void gsk_pango_renderer_release (GskPangoRenderer *crenderer); -- 2.30.2